﻿using System;
using System.ComponentModel;
using System.Web;
using System.Web.UI;
using System.Web.UI.WebControls.WebParts;
using Microsoft.SharePoint;
using Microsoft.SharePoint.Utilities;
using System.Text;
//using System.Reflection;
//using System.Diagnostics;
using System.Collections;

namespace SharePoint.List.Field
{
    [ToolboxItemAttribute(false)]
    public class Manager : WebPart
    {
        // For Sandboxed Code I altered;
        // OnLoad and OnUnload - Decided to show a different method for site access
        // Versioning - Can't use Assembly
        // Using - to remove unused namespaces
        // Render - Update use of Version class
        // CreateChildControls - No Reference to ASCX - Can't Use Them
        // _ascxPath was removed as not used.
        // We do not override DesignTimeHTML
        // We do not use Resources

        protected override void CreateChildControls()
        {
        }

        SPWeb objWeb;
        StringBuilder sbErrorText = new StringBuilder();

        #region Override OnLoad
        protected override void OnLoad(EventArgs e)
        {
            try
            {
                base.OnLoad(e);
                //I can use SPContext.Current.Web here but why not do something different.

                SPSite oSite = new SPSite(HttpContext.Current.Request.Url.ToString());
                if (oSite != null)
                {
                    objWeb = oSite.OpenWeb();
                    oSite.Dispose();
                }
            }
            catch
            {
            }
        }
        #endregion

        #region Override OnUnload
        protected override void OnUnload(EventArgs e)
        {
            try
            {
                base.OnUnload(e);
                if (objWeb != null)
                    objWeb.Dispose();
            }
            catch
            {
            }
        }
        #endregion        

        #region CustomError
        internal StringBuilder CustomError(Exception Error)
        {
            if (System.Web.HttpContext.Current.Request["StackTrace"] != null && System.Web.HttpContext.Current.Request["StackTrace"].ToLower().Equals("true"))
                return new StringBuilder(string.Format("<b> An Error Occured: </b><br/><b>Error: </b>{0}<br/>", SPEncode.HtmlEncode(Error.Message)));
            else
                return new StringBuilder(string.Format("<b> An Error Occured: </b><br/><b>Error: </b>{0}<br/><b>Trace: </b>{1}<br/>", SPEncode.HtmlEncode(Error.Message), SPEncode.HtmlEncode(Error.StackTrace)));
        }
        #endregion

        #region Versioning
        public void ShowVersion(HtmlTextWriter output, string _ProductName, string _Company, string _Copyright, string _FileVersion)
        {
            try
            {
                output.Write("<table border=0>");
                output.Write("<tr align=left valign=top><td><b>Application:</b></td><td>" + _ProductName + "</td></tr>");
                output.Write("<tr align=left valign=top><td><b>Organization:</b></td><td>" + _Company + "</td></tr>");
                output.Write("<tr align=left valign=top><td><b>Version:</b></td><td>" + _FileVersion + "</td></tr>");
                output.Write("<tr align=left valign=top><td colspan=\"2\">&nbsp;</td></tr>");
                output.Write("<tr align=left valign=top><td colspan=\"2\">" + _Copyright + "</td></tr>");
                output.Write("<tr align=left valign=top><td colspan=\"2\">Warning: This computer program is protected by copyright law and international treaties. Unauthorized reproduction or distribution of this program, or any portion of it, may result in severe civil and criminal penalties, and will be prosecuted to the maximum extent possible under the law.</td></tr>");
                output.Write("<tr align=left valign=top><td colspan=\"2\">&nbsp;</td></tr>");
                output.Write("<tr align=left valign=top><td><b>&nbsp;</b></td><td><b><<a href=\"" + System.Web.HttpContext.Current.Request.Url.AbsoluteUri.ToLower().Replace("?version=true", "").Replace("&version=true", "") + "\">Close Version Window</a>></b></td></tr>");
                output.Write("</table>");
            }
            catch (Exception Error)
            {
                output.Write(CustomError(Error).ToString());
            }
        }
        #endregion

        #region Render
        protected override void Render(HtmlTextWriter output)
        {
            base.Render(output);

            if (this.Parent.GetType().FullName == "Microsoft.SharePoint.WebPartPages.WebPartPreview")
            {
                output.Write("<img src=\"" + objWeb.Site.Url.ToString() + "/SiteAssets/ImageOfSLFM.png\"/>");
                objWeb.Site.Dispose();
            }
            else
            {
                objWeb.Site.Dispose();
                if ((Page.Request["Version"] != null) && (Page.Request["Version"].ToLower().Equals("true")))
                {
                    ShowVersion(output, "SharePoint List Field Manager", "CorasWorks Corporation", "Copyright &#169; CorasWorks 2010", "2.0.0.1");
                }
                else
                {
                    try
                    {
                        if (objWeb.DoesUserHavePermissions(SPBasePermissions.ManageLists))
                        {
                            //Initiate Request
                            bool FieldUpdated = false;
                            #region Update the Field
                            if ((Page.Request["submittype"] != null) && (Page.Request["submittype"] == "savesettings"))
                            {
                                if (Page.Request["cw_lfm_lists"] != "" && Page.Request["cw_lfm_fields"] != "")
                                {
                                    try
                                    {
                                        SPField objField = GetField(Page.Request["cw_lfm_lists"], Page.Request["cw_lfm_siteurl"], Page.Request["cw_lfm_fields"]);
                                        try
                                        {
                                            if (Page.Request["cw_lfm_field_allowdeletion"] == "on")
                                                objField.AllowDeletion = true;
                                            else
                                                objField.AllowDeletion = false;
                                        }
                                        catch (Exception Error) { sbErrorText.Append(CustomError(Error)); }
                                        try
                                        {
                                            if (Page.Request["cw_lfm_field_hidden"] == "on")
                                                objField.Hidden = true;
                                            else
                                                objField.Hidden = false;
                                        }
                                        catch (Exception Error) { sbErrorText.Append(CustomError(Error)); }
                                        try
                                        {
                                            if (Page.Request["cw_lfm_field_readonly"] == "on")
                                                objField.ReadOnlyField = true;
                                            else
                                                objField.ReadOnlyField = false;
                                        }
                                        catch (Exception Error) { sbErrorText.Append(CustomError(Error)); }
                                        try
                                        {
                                            if (Page.Request["cw_lfm_field_showindisplayform"] == "on")
                                                objField.ShowInDisplayForm = true;
                                            else
                                                objField.ShowInDisplayForm = false;
                                        }
                                        catch (Exception Error) { sbErrorText.Append(CustomError(Error)); }
                                        try
                                        {
                                            if (Page.Request["cw_lfm_field_showineditform"] == "on")
                                                objField.ShowInEditForm = true;
                                            else
                                                objField.ShowInEditForm = false;
                                        }
                                        catch (Exception Error) { sbErrorText.Append(CustomError(Error)); }
                                        try
                                        {
                                            if (Page.Request["cw_lfm_field_showinlistsettings"] == "on")
                                                objField.ShowInListSettings = true;
                                            else
                                                objField.ShowInListSettings = false;
                                        }
                                        catch (Exception Error) { sbErrorText.Append(CustomError(Error)); }
                                        try
                                        {
                                            if (Page.Request["cw_lfm_field_showinnewform"] == "on")
                                                objField.ShowInNewForm = true;
                                            else
                                                objField.ShowInNewForm = false;
                                        }
                                        catch (Exception Error) { sbErrorText.Append(CustomError(Error)); }
                                        try
                                        {
                                            if (Page.Request["cw_lfm_field_showinversionhistory"] == "on")
                                                objField.ShowInVersionHistory = true;
                                            else
                                                objField.ShowInVersionHistory = false;
                                        }
                                        catch (Exception Error) { sbErrorText.Append(CustomError(Error)); }
                                        try
                                        {
                                            if (Page.Request["cw_lfm_field_showinviewforms"] == "on")
                                                objField.ShowInViewForms = true;
                                            else
                                                objField.ShowInViewForms = false;
                                        }
                                        catch (Exception Error) { sbErrorText.Append(CustomError(Error)); }
                                        objField.Update();
                                    }
                                    catch (Exception Error) { sbErrorText.Append(CustomError(Error)); }
                                    FieldUpdated = true;
                                }
                            }
                            #endregion

                            //Output Form
                            int intFormLevel = 0;
                            if (Page.Request["submittype"] != null && !Page.Request["submittype"].Equals(""))
                            {
                                intFormLevel = 1;
                                if (Page.Request["submittype"] == "showfields")
                                    intFormLevel = 2;
                                if (Page.Request["submittype"] == "showfieldsettings")
                                    intFormLevel = 3;
                                if (Page.Request["submittype"] == "savesettings")
                                    intFormLevel = 4;
                            }

                            #region BeginTable
                            output.Write("<input type=\"hidden\" name=\"submittype\" id=\"submittype\" value=\"\"/>");
                            output.Write("<table border=\"0\">");
                            output.Write("<tr><td colspan=\"2\" align=\"center\" bgcolor=\"#696969\"><b><font color=\"#FFFFFF\">List Field Manager</font></b></td></tr>");
                            //Site Selection
                            output.Write("<tr><td valign=\"top\" align=\"right\" width=\"180px\"><b>Site URL:</b></td><td valign=\"top\" align=\"left\"><input type=\"text\" value=\"" + (Page.Request["cw_lfm_siteurl"] ?? "") + "\" name=\"cw_lfm_siteurl\"></td></tr>");
                            output.Write("<tr><td align=\"right\"><b></b></td><td><input onClick=\"document.getElementById('submittype').value = 'showlists';\" type=\"submit\" name=\"cw_lfm_showlists\" value=\"Display Lists\"></td></tr>");
                            if (intFormLevel >= 1)
                            {
                                output.Write("<tr><td colspan=\"2\"><hr></td></tr>");
                                //List Selection
                                output.Write("<tr><td valign=\"top\" align=\"right\"><b>List:</b></td><td valign=\"top\" align=\"left\">");
                                output.Write(GetLists(Page.Request["cw_lfm_lists"], Page.Request["cw_lfm_siteurl"]));
                                output.Write("</td></tr>");
                                output.Write("<tr><td align=\"right\"><b></b></td><td><input onClick=\"document.getElementById('submittype').value = 'showfields';\"type=\"submit\" name=\"cw_lfm_showfields\" value=\"Display Fields\"></td></tr>");

                                if (intFormLevel >= 2 && !Page.Request["cw_lfm_lists"].Equals(""))
                                {
                                    output.Write("<tr><td colspan=\"2\"><hr></td></tr>");
                                    //Field Selection
                                    output.Write("<tr><td valign=\"top\" align=\"right\"><b>Field:</b></td><td valign=\"top\" align=\"left\">");
                                    output.Write(GetFields(Page.Request["cw_lfm_lists"], Page.Request["cw_lfm_siteurl"], Page.Request["cw_lfm_fields"]));
                                    output.Write("</td></tr>");
                                    output.Write("<tr><td align=\"right\"><b></b></td><td><input onClick=\"document.getElementById('submittype').value = 'showfieldsettings';\" type=\"submit\" name=\"cw_lfm_showfieldsettings\" value=\"Display Field Settings\"></td></tr>");
                                    if (intFormLevel >= 3)
                                    {
                                        SPField objField = GetField(Page.Request["cw_lfm_lists"], Page.Request["cw_lfm_siteurl"], Page.Request["cw_lfm_fields"]);
                                        if (objField != null)
                                        {
                                            output.Write("<tr><td colspan=\"2\"><hr></td></tr>");
                                            //Field Setup
                                            //Hidden
                                            output.Write("<tr><td align=\"right\"><b>Hidden:</b></td><td valign=\"top\" align=\"left\"><input type=\"checkbox\" name=\"cw_lfm_field_hidden\" " + (objField.Hidden.ToString().ToLower() == "true" ? "checked" : "") + "></td></tr>");
                                            //ReadOnlyField
                                            output.Write("<tr><td align=\"right\"><b>Read Only:</b></td><td valign=\"top\" align=\"left\"><input type=\"checkbox\" name=\"cw_lfm_field_readonly\" " + (objField.ReadOnlyField.ToString().ToLower() == "true" ? "checked" : "") + "></td></tr>");
                                            //ShowInDisplayForm
                                            output.Write("<tr><td align=\"right\"><b>Show In Display Form:</b></td><td valign=\"top\" align=\"left\"><input type=\"checkbox\" name=\"cw_lfm_field_showindisplayform\" " + (objField.ShowInDisplayForm.ToString().ToLower() == "true" ? "checked" : "") + "></td></tr>");
                                            //ShowInEditForm
                                            output.Write("<tr><td align=\"right\"><b>Show In Edit Form:</b></td><td valign=\"top\" align=\"left\"><input type=\"checkbox\" name=\"cw_lfm_field_showineditform\" " + (objField.ShowInEditForm.ToString().ToLower() == "true" ? "checked" : "") + "></td></tr>");
                                            //ShowInNewForm
                                            output.Write("<tr><td align=\"right\"><b>Show In New Form:</b></td><td valign=\"top\" align=\"left\"><input type=\"checkbox\" name=\"cw_lfm_field_showinnewform\" " + (objField.ShowInNewForm.ToString().ToLower() == "true" ? "checked" : "") + "></td></tr>");
                                            //ShowInListSettings
                                            output.Write("<tr><td align=\"right\"><b>Show In List Settings:</b></td><td valign=\"top\" align=\"left\"><input type=\"checkbox\" name=\"cw_lfm_field_showinlistsettings\" " + (objField.ShowInListSettings.ToString().ToLower() == "true" ? "checked" : "") + "></td></tr>");
                                            //ShowInViewForms
                                            output.Write("<tr><td align=\"right\"><b>Show In Views:</b></td><td valign=\"top\" align=\"left\"><input type=\"checkbox\" name=\"cw_lfm_field_showinviewforms\" " + (objField.ShowInViewForms.ToString().ToLower() == "true" ? "checked" : "") + "></td></tr>");
                                            //AllowDeletion
                                            output.Write("<tr><td align=\"right\"><b>Allow Deletion:</b></td><td valign=\"top\" align=\"left\"><input type=\"checkbox\" name=\"cw_lfm_field_allowdeletion\" " + (objField.AllowDeletion.ToString().ToLower() == "true" ? "checked" : "") + "></td></tr>");
                                            //ShowInVersionHistory
                                            output.Write("<tr><td align=\"right\"><b>Show In Version History:</b></td><td valign=\"top\" align=\"left\"><input type=\"checkbox\" name=\"cw_lfm_field_showinversionhistory\" " + (objField.ShowInVersionHistory.ToString().ToLower() == "true" ? "checked" : "") + "></td></tr>");
                                            
                                            output.Write("<tr><td colspan=\"2\"><hr></td></tr>");
                                            output.Write("<tr><td align=\"right\"><b></b></td><td><input onClick=\"document.getElementById('submittype').value = 'savesettings';\" type=\"submit\" name=\"cw_lfm_savesettings\" value=\"Save Settings\"></td></tr>");
                                        }
                                        if (FieldUpdated)
                                        {
                                            output.Write("<tr><td colspan=\"2\"><hr></td></tr>");
                                            output.Write("<tr><td align=\"right\"><b>Status:</td><td>Field Updated</td></tr>");
                                        }
                                    }
                                }
                            }
                            output.Write("</table>");
                            #endregion
                        }
                        else
                        {
                            output.Write("<b>You Must Have List Admin Right to Use This Web Part</b>");
                        }
                    }
                    catch (Exception Error)
                    {
                        sbErrorText.Append(CustomError(Error));
                    }
                }

                if (Page.Request["Debug"] != null && Page.Request["Debug"].ToLower().Equals("true"))
                    output.Write("<br/>" + sbErrorText.ToString() + "<br/>");
            }
        }
        #endregion

        #region GetLists
        private StringBuilder GetLists(string ListGUID, string SiteURL)
        {
            string _ReturnError = "<select name=\"cw_lfm_lists\"><option selected value=\"\">Please Select a List</option></select><br/><b>Error: </b>{0}<br/>";
            try
            {
                StringBuilder sbLists = new StringBuilder();
                sbLists.Append("<select name=\"cw_lfm_lists\">");

                if (ListGUID != null && !ListGUID.Equals(""))
                    sbLists.Append("<option value=\"\">Please Select a List</option>");
                else
                    sbLists.Append("<option value=\"\" selected>Please Select a List</option>");

                if (SiteURL.Equals(""))
                {
                    foreach (SPList objList in objWeb.Lists)
                    {
                        if (objList.ID.ToString().Equals(ListGUID))
                            sbLists.Append("<option selected value=\"" + objList.ID.ToString() + "\">" + objList.Title + "</option>");
                        else
                            sbLists.Append("<option value=\"" + objList.ID.ToString() + "\">" + objList.Title + "</option>");
                    }
                }
                else
                {
                    using (SPSite oSite = new SPSite(SiteURL))
                    {
                        if (oSite != null)
                        {
                            using (SPWeb objNewWeb = oSite.OpenWeb())
                            {
                                foreach (SPList objList in objNewWeb.Lists)
                                {
                                    if (objList.ID.ToString().Equals(ListGUID ?? ""))
                                        sbLists.Append("<option selected value=\"" + objList.ID.ToString() + "\">" + objList.Title + "</option>");
                                    else
                                        sbLists.Append("<option value=\"" + objList.ID.ToString() + "\">" + objList.Title + "</option>");
                                }
                            }
                        }
                        else
                        {
                            return new StringBuilder().Append(String.Format(_ReturnError, "Site Does Not Exist or You Do Not Have Access<br/>"));
                        }
                    }
                }
                sbLists.Append("</select>");
                return sbLists;
            }
            catch (Exception Error)
            {
                return new StringBuilder().Append(String.Format(_ReturnError, Error.Message.ToString()));
            }
        }
        #endregion

        #region GetFields
        private StringBuilder GetFields(string ListGUID, string SiteURL, string FieldID)
        {
            try
            {
                StringBuilder sbLists = new StringBuilder();
                sbLists.Append("<select name=\"cw_lfm_fields\">");

                if (FieldID != null && !FieldID.Equals(""))
                    sbLists.Append("<option value=\"\">Please Select a Field</option>");
                else
                    sbLists.Append("<option value=\"\" selected>Please Select a Field</option>");

                if (ListGUID != null && !ListGUID.Equals(""))
                {
                    if (SiteURL.Equals(""))
                    {
                        SPFieldCollection objFields = objWeb.Lists[new Guid(ListGUID)].Fields;
                        foreach (SPField objField in objFields)
                        {
                            if (objField.Id.ToString().Equals(FieldID ?? ""))
                                sbLists.Append("<option selected value=\"" + objField.Id.ToString() + "\">" + objField.Title + "</option>");
                            else
                                sbLists.Append("<option value=\"" + objField.Id.ToString() + "\">" + objField.Title + "</option>");
                        }
                    }
                    else
                    {
                        using (SPSite oSite = new SPSite(SiteURL))
                        {
                            using (SPWeb objNewWeb = oSite.OpenWeb())
                            {
                                SPFieldCollection objFields = objNewWeb.Lists[new Guid(ListGUID)].Fields;
                                //Load Up Field into Array so it can be sorted.
                                System.Collections.ArrayList HoldFields = new ArrayList();
                                foreach (SPField objField in objFields)
                                {
                                    HoldFields.Add(objField.Title.ToString() + ":" + objField.Id.ToString());
                                }
                                HoldFields.Sort();
                                foreach (string sItem in HoldFields)
                                {
                                    string strID = sItem.Split(':').GetValue(1).ToString();
                                    string strTitle = sItem.Split(':').GetValue(0).ToString();

                                    if (strID.Equals(FieldID ?? ""))
                                        sbLists.Append("<option selected value=\"" + strID + "\">" + strTitle + "</option>");
                                    else
                                        sbLists.Append("<option value=\"" + strID + "\">" + strTitle + "</option>");
                                }
                            }
                        }
                    }
                }
                sbLists.Append("</select>");
                return sbLists;
            }
            catch (Exception Error)
            {
                return new StringBuilder().Append("<select name=\"cw_lfm_fields\"><option selected value=\"\">Please Select a Field</option></select><br/><b>Error: </b>" + Error.Message.ToString() + "<br/>");
            }
        }
        #endregion

        #region GetField
        private SPField GetField(string ListGUID, string SiteURL, string FieldID)
        {
            StringBuilder sbLists = new StringBuilder();

            if (!ListGUID.Equals("") && !FieldID.Equals(""))
            {
                if (SiteURL.Equals(""))
                {
                    return objWeb.Lists[new Guid(ListGUID)].Fields[new Guid(FieldID)];
                }
                else
                {
                    using (SPSite oSite = new SPSite(SiteURL))
                    {
                        using (SPWeb objNewWeb = oSite.OpenWeb())
                        {
                            return objNewWeb.Lists[new Guid(ListGUID)].Fields[new Guid(FieldID)];
                        }
                    }
                }
            }
            return null;
        }
        #endregion
    }
}

